// render函数 负责将一个vnode渲染成一个真实的dom
// h函数 负责创建一个vnode

import { h, render } from "vue";
import type { CreateMessageProps, MessageContext } from "./types";
import MessageConstructor from "./index.vue";

// 创建数组，用于存储组件实例
const instances: MessageContext[] = reactive([]);
let seed = 1;

export function createMessage(props: CreateMessageProps) {
  const id = `message_${seed++}`;
  // 1.创建dom
  const container = document.createElement("div");

  // 移除节点
  const destory = () => {
    const idx = instances.findIndex((instance) => instance.id === id);
    if (idx === -1) return;
    instances.splice(idx, 1);
    render(null, container);
  };

  const newProps = {
    ...props,
    onDestroy: destory,
    id: id,
  };

  // 2.创建vnode
  const vnode = h(MessageConstructor, newProps);

  // 3.渲染vnode
  render(vnode, container);
  // 4.将dom元素添加到body中
  document.body.appendChild(container.firstElementChild!);

  // 创建组件实例
  const vm = vnode.component!;
  const instance: MessageContext = {
    id: id,
    vnode,
    props: newProps,
    vm: vm,
  };

  instances.push(instance);

  return instance;
}

// 可以获取最后一个实例
export function getLastInstance() {
  return instances[instances.length - 1];
}

//获取上一个实例最下面的坐标位置
export function getLastBottomOffset(id: string) {
  const idx = instances.findIndex((instance) => instance.id === id);
  if (idx <= 0) {
    return 0;
  } else {
    const prev = instances[idx - 1];
    return prev.vm.exposed!.bottomOffset.value;
  }
}
